﻿//using System;
//using System.Collections.Generic;
//using System.Linq;
//using System.Text;
//using SmartSpace.Core.Metadata;
//using SmartSpace.Core.Metadata.Workflow;
//using SmartSpace.Core.Base;

//namespace SmartSpace.Core
//{
//    public class MetadataService : IMetadataService
//    {
//        protected SsDbContext _context { get; private set; }
//        private ContextFactory _contextFactory { get; set; }

//        public MetadataService(SsDbContext context, ContextFactory contextFactory)
//        {
//            _context = context;
//            _contextFactory = contextFactory;
//        }

//        public List<EntityMetadata> FindEntities(int start, int limit)
//        {
//            using (SsDbContext context = _contextFactory.GetValue())
//            {
//                List<EntityMetadata> list = context.Set<EntityMetadata>()
//                    .OrderByDescending(p => p.Name)
//                    .Skip(start)
//                    .Take(limit)
//                    .ToList();
//                PagedList<EntityMetadata> pagedList = new PagedList<EntityMetadata>();
//                foreach (EntityMetadata item in list)
//                {
//                    item.Properties = context.Set<PropertyMetadata>()
//                        .Include("Type")
//                        .Where(p => p.EntityId == item.Id)
//                        .OrderBy(p => p.SortIndex)
//                        .ToList();
//                    pagedList.Add(item);
//                }
//                pagedList.Start = start;
//                pagedList.Limit = limit;
//                pagedList.Total = context.Set<EntityMetadata>().Count();

//                return pagedList;
//            }
//        }

//        public EntityMetadata FindEntity(Guid id)
//        {
//            using (SsDbContext context = _contextFactory.GetValue())
//            {
//                EntityMetadata entity = context.Set<EntityMetadata>()
//                    .Where(p => p.Id == id)
//                    .FirstOrDefault();
//                entity.Properties = context.Set<PropertyMetadata>()
//                    .Include("Type")
//                    .Where(p => p.EntityId == entity.Id)
//                    .OrderBy(p => p.SortIndex)
//                    .ToList();

//                return entity;
//            }
//        }

//        public bool StoreEntity(EntityMetadata metadata)
//        {
//            using (SsDbContext context = _contextFactory.GetValue())
//            {
//                foreach (PropertyMetadata property in metadata.Properties)
//                {
//                    property.Type = null;
//                }

//                if (context.Set<EntityMetadata>()
//                    .Where(p => p.Id == metadata.Id)
//                    .Select(p => new { p.Id })
//                    .FirstOrDefault() == null)
//                {
//                    context.Set<EntityMetadata>().Add(metadata);
//                }
//                else
//                {
//                    List<PropertyMetadata> properties = context.Set<PropertyMetadata>()
//                        .Where(p => p.EntityId == metadata.Id)
//                        .ToList();
//                    foreach (PropertyMetadata pro in properties)
//                    {
//                        bool isExist = false;
//                        PropertyMetadata updatePro = null;
//                        foreach (PropertyMetadata proNew in metadata.Properties)
//                        {
//                            if (proNew.Id == pro.Id)
//                            {
//                                updatePro = proNew;
//                                isExist = true;
//                                break;
//                            }
//                        }

//                        if (!isExist)
//                        {
//                            // 删除
//                            context.Set<PropertyMetadata>().Remove(pro);
//                        }
//                        else
//                        {
//                            // 更新
//                            context.Entry(pro).State = System.Data.Entity.EntityState.Detached;
//                            context.Entry(updatePro).State = System.Data.Entity.EntityState.Modified;
//                        }
//                    }

//                    foreach (PropertyMetadata proNew in metadata.Properties)
//                    {
//                        bool isExist = false;
//                        foreach (PropertyMetadata pro in properties)
//                        {
//                            if (proNew.Id == pro.Id)
//                            {
//                                isExist = true;
//                                break;
//                            }
//                        }

//                        if (!isExist)
//                        {
//                            // 添加
//                            context.Set<PropertyMetadata>().Add(proNew);
//                        }
//                    }

//                    context.Entry(metadata).State = System.Data.Entity.EntityState.Modified;

//                }

//                int count = context.SaveChanges();
//                return true;
//            }
//        }

//        public List<WorkflowMetadata> FindWorkflows(int start, int limit)
//        {
//            using (SsDbContext context = _contextFactory.GetValue())
//            {
//                List<WorkflowMetadata> list = context.Set<WorkflowMetadata>()
//                    .Include("Entity")
//                    .Include("Entity.Properties")
//                    .Include("Activities")
//                    .Include("Activities.Events")
//                    .Include("Activities.ModuleView")
//                    .Include("Activities.ModuleView.Entity")
//                    .Include("Activities.ModuleView.Fields")
//                    .Include("Activities.ModuleView.Fields.Property")
//                    .OrderByDescending(p => p.Caption)
//                    .Skip(start)
//                    .Take(limit)
//                    .ToList();
//                PagedList<WorkflowMetadata> pagedList = new PagedList<WorkflowMetadata>();
//                foreach (WorkflowMetadata item in list)
//                {
//                    pagedList.Add(item);
//                }
//                pagedList.Start = start;
//                pagedList.Limit = limit;
//                pagedList.Total = context.Set<WorkflowMetadata>().Count();

//                return pagedList;
//            }
//        }

//        public WorkflowMetadata FindWorkflow(Guid id)
//        {
//            using (SsDbContext context = _contextFactory.GetValue())
//            {
//                return context.Set<WorkflowMetadata>()
//                    .Include("Entity")
//                    .Include("Entity.Properties")
//                    .Include("Entity.Properties.Type")
//                    .Include("Activities")
//                    .Include("Activities.Events")
//                    .Include("Activities.Rights")
//                    .Include("Activities.Rights.Role")
//                    .Include("Activities.Rights.FieldRights")
//                    .Include("Activities.Rights.FieldRights.Field")
//                    .Include("Activities.ModuleView")
//                    .Include("Activities.ModuleView.Entity")
//                    .Include("Activities.ModuleView.Fields")
//                    .Include("Activities.ModuleView.Fields.Property")
//                    .Where(p => p.Id == id)
//                    .FirstOrDefault();
//            }
//        }

//        public bool StoreWorkflow(WorkflowMetadata metadata)
//        {
//            using (SsDbContext context = _contextFactory.GetValue())
//            {
//                metadata.Entity = null;

//                foreach (ActivityMetadata activity in metadata.Activities)
//                {
//                    activity.Workflow = null;
//                    activity.ModuleView.Entity = null;
//                    foreach (FieldMetadata field in activity.ModuleView.Fields)
//                    {
//                        field.Property = null;
//                        field.ModuleView = null;
//                    }

//                    if (activity.Events != null)
//                    {
//                        foreach (EventMetadata @event in activity.Events)
//                        {
//                            @event.FormActivity = null;
//                            @event.ToActivity = null;
//                        }
//                    }

//                    if (activity.Rights != null)
//                    {
//                        foreach (ActivityRight right in activity.Rights)
//                        {
//                            right.Activity = null;
//                            right.Role = null;
//                            if (right.FieldRights != null)
//                            {
//                                foreach (FieldRight fieldRight in right.FieldRights)
//                                {
//                                    fieldRight.Activity = null;
//                                    fieldRight.Field = null;
//                                    fieldRight.Role = null;
//                                }
//                            }
//                        }
//                    }
//                }

//                if (context.Set<WorkflowMetadata>()
//                    .Where(p => p.Id == metadata.Id)
//                    .Select(p => new { p.Id })
//                    .FirstOrDefault() == null)
//                {
//                    context.Set<WorkflowMetadata>().Add(metadata);
//                }
//                else
//                {
//                    OnStoreActivities(metadata, context);
//                    context.Entry(metadata).State = System.Data.Entity.EntityState.Modified;
//                }

//                context.SaveChanges();
//                return true;
//            }
//        }

//        public bool StoreLayout(WorkflowDiagram layout)
//        {
//            using (SsDbContext context = _contextFactory.GetValue())
//            {
//                if (context.Set<WorkflowDiagram>()
//                    .Where(p => p.Id == layout.Id)
//                    .Select(p => new { p.Id })
//                    .FirstOrDefault() == null)
//                {
//                    context.Set<WorkflowDiagram>().Add(layout);
//                }
//                else
//                {
//                    context.Entry<WorkflowDiagram>(layout).State = System.Data.Entity.EntityState.Modified;
//                }

//                context.SaveChanges();
//                return true;
//            }
//        }

//        public WorkflowDiagram FindLayout(Guid id)
//        {
//            using (SsDbContext context = _contextFactory.GetValue())
//            {
//                return context.Set<WorkflowDiagram>()
//                    .Where(p => p.Id == id)
//                    .FirstOrDefault();
//            }
//        }

//        //public bool StoreType(TypeMetadata metadata)
//        //{
//        //    using (SsDbContext context = _contextFactory.GetValue())
//        //    {
//        //        if (context.Set<TypeMetadata>()
//        //            .Where(p => p.Id == metadata.Id)
//        //            .Select(p => new { p.Id })
//        //            .FirstOrDefault() == null)
//        //        {
//        //            context.Set<TypeMetadata>().Add(metadata);
//        //        }
//        //        else
//        //        {
//        //            context.Set<TypeMetadata>().Attach(metadata);
//        //        }

//        //        context.SaveChanges();
//        //        return true;
//        //    }
//        //}

//        //public PagedList<TypeMetadata> FindTypes(int start, int limit)
//        //{
//        //    List<TypeMetadata> list = _context.Set<TypeMetadata>()
//        //        .OrderByDescending(p => p.Caption)
//        //        .Skip(start)
//        //        .Take(limit)
//        //        .ToList();
//        //    PagedList<TypeMetadata> pagedList = new PagedList<TypeMetadata>();
//        //    foreach (TypeMetadata item in list)
//        //    {
//        //        pagedList.Add(item);
//        //    }
//        //    pagedList.Start = start;
//        //    pagedList.Limit = limit;
//        //    pagedList.Total = _context.Set<TypeMetadata>().Count();

//        //    return pagedList;
//        //}

//        //public TypeMetadata FindType(Guid id)
//        //{
//        //    using (SsDbContext context = _contextFactory.GetValue())
//        //    {
//        //        return context.Set<TypeMetadata>()
//        //            .Where(p => p.Id == id)
//        //            .FirstOrDefault();
//        //    }
//        //}

//        //public bool StoreParser(TypeUIParser parser)
//        //{
//        //    using (SsDbContext context = _contextFactory.GetValue())
//        //    {
//        //        parser.Type = null;

//        //        if (context.Set<TypeUIParser>()
//        //            .Where(p => p.TypeId == parser.TypeId)
//        //            .Select(p => new { p.Id })
//        //            .FirstOrDefault() == null)
//        //        {
//        //            context.Set<TypeUIParser>().Add(parser);
//        //        }
//        //        else
//        //        {
//        //            context.Set<TypeUIParser>().Attach(parser);
//        //        }

//        //        context.SaveChanges();
//        //        return true;
//        //    }
//        //}

//        //public TypeUIParser FindParser(TypeMetadata type)
//        //{
//        //    using (SsDbContext context = _contextFactory.GetValue())
//        //    {
//        //        return context.Set<TypeUIParser>()
//        //            .Where(p => p.TypeId == type.Id)
//        //            .FirstOrDefault();
//        //    }
//        //}

//        private void OnStoreActivities(WorkflowMetadata metadata, SsDbContext context)
//        {
//            List<ActivityMetadata> activities = context.Set<ActivityMetadata>()
//                .Where(p => p.WorkflowId == metadata.Id)
//                .ToList();

//            foreach (ActivityMetadata item in metadata.Activities)
//            {
//                bool isExist = false;
//                foreach (ActivityMetadata activity in activities)
//                {
//                    if (item.Id == activity.Id)
//                    {
//                        isExist = true;
//                        break;
//                    }
//                }

//                if (!isExist)
//                {
//                    context.Set<ActivityMetadata>().Add(item);
//                }
//            }

//            foreach (ActivityMetadata activity in activities)
//            {
//                ActivityMetadata newActivity = null;
//                bool isExist = false;
//                foreach (ActivityMetadata item in metadata.Activities)
//                {
//                    if (item.Id == activity.Id)
//                    {
//                        isExist = true;
//                        newActivity = item;
//                        break;
//                    }
//                }
//                if (isExist)
//                {
//                    // 更新已有的activity
//                    context.Entry(activity).State = System.Data.Entity.EntityState.Detached;

//                    this.OnStoreView(newActivity, context);
//                    this.OnStoreEvents(newActivity, context);
//                    this.OnStoreRights(newActivity, context);

//                    // 更新activity的视图信息
//                    context.Entry(newActivity).State = System.Data.Entity.EntityState.Modified;
//                }
//                else
//                {
//                    context.Set<ActivityMetadata>().Remove(activity);
//                }
//            }
//        }

//        private void OnStoreView(ActivityMetadata activity, SsDbContext context)
//        {
//            List<FieldMetadata> fields = context.Set<FieldMetadata>()
//                .Where(p=>p.ViewId == activity.ModuleView.Id)
//                .ToList();

//            foreach (FieldMetadata field in fields)
//            {
//                FieldMetadata newField = null;
//                bool isExist = false;
//                foreach (FieldMetadata item in activity.ModuleView.Fields)
//                {
//                    if (item.Id == field.Id)
//                    {
//                        isExist = true;
//                        newField = item;
//                        break;
//                    }
//                }
//                if (isExist)
//                {
//                    // 更新已有的activity
//                    context.Entry(field).State = System.Data.Entity.EntityState.Detached;
//                    // 更新activity的视图信息
//                    context.Entry(newField).State = System.Data.Entity.EntityState.Modified;
//                }
//            }

//            foreach (FieldMetadata item in activity.ModuleView.Fields)
//            {
//                bool isExist = false;
//                foreach (FieldMetadata field in fields)
//                {
//                    if (item.Id == field.Id)
//                    {
//                        isExist = true;
//                        break;
//                    }
//                }

//                if (!isExist)
//                {
//                    context.Set<FieldMetadata>().Add(item);
//                }
//            }
//        }

//        private void OnStoreEvents(ActivityMetadata activity, SsDbContext context)
//        {
//            //foreach (EventMetadata item in activity.Events)
//            //{
//            //    foreach (EventToObject toOjbect in item.ToObjects)
//            //    {
//            //        toOjbect.Event = null;
//            //    }
//            //}

//            List<EventMetadata> events = context.Set<EventMetadata>()
//                .Where(p => p.FormActivityId == activity.Id)
//                .ToList();

//            foreach (EventMetadata @event in events)
//            {
//                EventMetadata newEvent = null;
//                bool isExist = false;
//                foreach (EventMetadata item in activity.Events)
//                {
//                    if (item.Id == @event.Id)
//                    {
//                        isExist = true;
//                        newEvent = item;
//                        break;
//                    }
//                }
//                if (isExist)
//                {
//                    context.Entry(@event).State = System.Data.Entity.EntityState.Detached;
//                    context.Entry(newEvent).State = System.Data.Entity.EntityState.Modified;
//                }
//            }

//            foreach (EventMetadata item in activity.Events)
//            {
//                bool isExist = false;
//                foreach (EventMetadata @event in events)
//                {
//                    if (item.Id == @event.Id)
//                    {
//                        isExist = true;
//                        break;
//                    }
//                }

//                if (!isExist)
//                {
//                    context.Set<EventMetadata>().Add(item);
//                }
//            }
//        }

//        private void OnStoreRights(ActivityMetadata activity, SsDbContext context)
//        {
//            List<ActivityRight> rights = context.Set<ActivityRight>()
//                .Where(p => p.ActivityId == activity.Id)
//                .ToList();

//            foreach (ActivityRight item in activity.Rights)
//            {
//                bool isExist = false;
//                foreach (ActivityRight right in rights)
//                {
//                    if (item.Id == right.Id)
//                    {
//                        isExist = true;
//                        break;
//                    }
//                }

//                if (!isExist)
//                {
//                    item.Role = null;
//                    item.Activity = null;
//                    context.Set<ActivityRight>().Add(item);
//                }
//            }

//            foreach (ActivityRight right in rights)
//            {
//                ActivityRight existRight = null;
//                bool isExist = false;
//                foreach (ActivityRight item in activity.Rights)
//                {
//                    if (item.Id == right.Id)
//                    {
//                        isExist = true;
//                        existRight = item;
//                        break;
//                    }
//                }
//                if (isExist)
//                {
//                    OnStoreFieldRights(existRight, context);

//                    context.Entry(right).State = System.Data.Entity.EntityState.Detached;
//                    existRight.Role = null;
//                    existRight.Activity = null;
//                    context.Entry(existRight).State = System.Data.Entity.EntityState.Modified;
//                }
//            }

//        }

//        private void OnStoreFieldRights(ActivityRight activityRight, SsDbContext context)
//        {
//            List<FieldRight> rights = context.Set<FieldRight>()
//                .Where(p => p.ActivityId == activityRight.ActivityId && p.RoleId == activityRight.RoleId)
//                .ToList();

//            foreach (FieldRight right in rights)
//            {
//                FieldRight existRight = null;
//                bool isExist = false;
//                foreach (FieldRight item in activityRight.FieldRights)
//                {
//                    if (item.Id == right.Id)
//                    {
//                        isExist = true;
//                        existRight = item;
//                        break;
//                    }
//                }
//                if (isExist)
//                {
//                    context.Entry(right).State = System.Data.Entity.EntityState.Detached;
//                    existRight.Role = null;
//                    existRight.Activity = null;
//                    existRight.Field = null;
//                    context.Entry(existRight).State = System.Data.Entity.EntityState.Modified;
//                }
//            }

//            foreach (FieldRight item in activityRight.FieldRights)
//            {
//                bool isExist = false;
//                foreach (FieldRight right in rights)
//                {
//                    if (item.Id == right.Id)
//                    {
//                        isExist = true;
//                        break;
//                    }
//                }

//                if (!isExist)
//                {
//                    item.Role = null;
//                    item.Activity = null;
//                    item.Field = null;
//                    context.Set<FieldRight>().Add(item);
//                }
//            }
//        }

//        public AuthorizedView FindView(ActivityMetadata activity, User user)
//        {
//            using (SsDbContext context = _contextFactory.GetValue())
//            {
//                List<RelationRoleToUser> roles = context.Set<RelationRoleToUser>()
//                    .Where(p => p.UserId == user.Id)
//                    .ToList();

//                AuthorizedView view = new AuthorizedView();
//                view.Id = activity.ModuleView.Id;
//                view.Caption = activity.ModuleView.Caption;
//                view.Entity = activity.ModuleView.Entity;
//                view.Fields = new List<AuthorizedField>();

//                // 获取字段信息
//                foreach (FieldMetadata fdMetadata in activity.ModuleView.Fields)
//                {
//                    AuthorizedField field = new AuthorizedField();
//                    field.Id = fdMetadata.Id;
//                    field.Property = fdMetadata.Property;
//                    field.SortIndex = fdMetadata.SortIndex;
//                    field.IsCanVisit = false;
//                    field.IsCanModify = false;

//                    // 设置字段的可访问权限
//                    foreach (ActivityRight right in activity.Rights)
//                    {
//                        #region 有一个权限可以访问，那么就可以访问
//                        if (right.IsAllowVisit)
//                        {
//                            view.IsCanVisit = true;
//                        }
//                        if (right.IsAllowModify)
//                        {
//                            view.IsCanModify = true;
//                        }
//                        if (right.IsAllowRemove)
//                        {
//                            view.IsCanRemove = true;
//                        }
//                        #endregion

//                        foreach (RelationRoleToUser role in roles)
//                        {
//                            if (role.RoleId == right.RoleId)
//                            {
//                                foreach (FieldRight fieldRight in right.FieldRights)
//                                {
//                                    if (fieldRight.FieldId == field.Id)
//                                    {
//                                        if (fieldRight.IsAllowVisit)
//                                        {
//                                            field.IsCanVisit = true;
//                                        }

//                                        if (fieldRight.IsAllowModify)
//                                        {
//                                            field.IsCanModify = true;
//                                        }
//                                    }
//                                    break;
//                                }
//                                break;
//                            }
//                        }
//                    }

//                    view.Fields.Add(field);
//                }


//                return view;
//            }
//        }
//    }
//}
